<?php
include('config.php');
include(lib_path.'/msg.php');
include(lib_path.'/common.fun.php');
define('BIN_PATH', $argv[2]);

echo 'CONNECTOIN_MSG_ID='.CONNECTOIN_MSG_ID.chr(10);
$db = new db($db_config[1], $db_config[2], $db_config[0], $db_config[3]);

//check config.php for more information about these messages
$link_msg = new msg(CONNECTOIN_MSG_ID, false);
$data_msg = new msg(DATA_MSG_ID, false);
$login_reg_msg = new msg(LOGIN_REG_MSG_ID, false);
$map_msg = new msg(MAP_MSG_ID, true);
$php_s_msg = new msg(DOWN_S_MSG_ID, false);

/*
$dis_data_msg = array(
			pid => new msg(DIS_DATA_MSG_ID+pid, false),
		);
*/
$dis_data_msg = array();
/*
$users[$fd] = array(uid, map_id, process id, login in time)
*/
$users = array();
/*
$maps2pids = array(
	mapid => array(
		pid=>total user numbers,
	),
);
*/
$maps2pids = array();

$sql = 'SELECT id,name,max_user FROM map';
$rows = $db->query($sql);
/*
map id to setting
$maps = array(
	map id=>array(map info )
);
*/
$maps = array();
foreach($rows as $row)
{
	$pid = startMapProcess($row['id']);
	$maps2pids[$row['id']][$pid] = 0;
	$maps[$row['id']] = $row;
}


while(1)
{
	$data_flag = false;
	$data = $link_msg->receive(true, $fd);
	if( $data && $fd>0 )
	{
		$data_flag = true;
		//echo 'Link data got:';
		if($data[0]==LINK_IN_MSG)
		{
			$users[$fd] = array('uid'=>0,'mid'=>0,'pid'=>0,'ltime'=>0);
			//echo $fd .' in';
		}else if($data[0]==LINK_OUT_MSG){
			if($users[$fd]['mid']>0&&$users[$fd]['pid']>0)
			{
				$login_reg_msg->send($users[$fd]['uid'].'', $fd);//通知注册登录进程保存用户数据到数据库
				$maps2pids[$users[$fd]['mid']][$users[$fd]['pid']]--;
			}
			$users[$fd] = array('uid'=>0,'mid'=>0,'pid'=>0,'ltime'=>0);
			//echo $fd .' out';
		}
		//echo chr(10);
	}

	$data = $map_msg->receive(true, $fd);
	if( $data && $fd>0 )
	{
		$data_flag = true;
		//array('fd'=>$fd,'user_id'=>$row['id'],'map_id'=>$row['map_id'])
		$my_pid = 0;
		$line_no = 0;
		foreach($maps2pids[$data['map_id']] as $pid=>$num)
		{
			$line_no++;
			if($maps[$data['map_id']]['max_user']>$num)
			{
				$my_pid = $pid;
				break;
			}
		}

		if(!$my_pid)
		{
			$line_no++;
			//if create new line process(service_game.php) failed, startMapProcess will make a log
			$my_pid = startMapProcess($data['map_id']);//auto create new line for a map
		}
		
		if($my_pid)
		{
			$users[$fd]['pid'] = $my_pid;
			$users[$fd]['mid'] = $data['map_id'];
			$users[$fd]['uid'] = $data['user_id'];
			$users[$fd]['ltime'] = time();
			//tell user he(she) entered a map
			$msg_text = $maps[$data['map_id']]['name'].'|'.$line_no.'|'.count($maps2pids[$data['map_id']]);
			$php_s_msg->send($msg_text, $fd);
			$dis_data_msg[$users[$fd]['pid']]->send($msg_text, $fd);
		}
	}

	$data = $data_msg->receive(true, $fd);
	if($data)
	{
		$data_flag = true;
		if(!isset($users[$fd])) $users[$fd] = array('uid'=>0,'mid'=>0,'pid'=>0,'ltime'=>0);
		if($users[$fd]['uid']==0)
		{//haven't logined
			$login_reg_msg->send($data, $fd);
		}else{
			$dis_data_msg[$users[$fd]['pid']]->send($data, $fd);
		}
	}
	if(!$data_flag) usleep(5000);
}

function startMapProcess($map_id)
{
	global $dis_data_msg;

	$pid = open_process($rs, BIN_PATH.' ');
	$dis_data_msg[$map_id][$pid] = new msg(DIS_DATA_MSG_ID+$pid, true);
	do_log('Start game process for : '.$map_id.' failed.');
}

function open_process(&$rs, $cmd, $mode = 'r')
{
	$rs = popen($cmd, $mode);
	return intval(fread($rs, 11));
}
